<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
    
</body>
<script>

    // JavaScript 的对象（Object），本质上是键值对的集合（Hash 结构），但是传统上只能用字符串当作键。(其他类型作为键名都会隐式转化为字符串 )

    // 传统的JS对象 => 键名都是字符串类型  => 能不能以其他类型的数据作为对象的键名?
    // 其他类型的数据作为对象的键名 => 数据会先隐式转化为字符串,再作为对象的键名
    // var data = {}

    // data[100] = 200;
    // data["hello"] = "world";
    // data[true] = false;
    // data[null] = undefined;

    // var arr = [1,2,3];
    // var obj = {a:1,b:2};
    
    // data[arr] = arr; // 用数组作为键名
    // data[obj] = obj; // 用对象作为键名

    // console.log(data);

    // for(var key in data){
    //     console.log(key, typeof key);
    // }

    // console.log(1,arr.toString()); "1,2,3"
    // console.log(1,obj.toString()); "[object Object]"



    // Map是对象的升级版!!!
    // 为了解决这个问题，ES6 提供了 Map 数据结构。它类似于对象，也是键值对的集合，但是“键”的范围不限于字符串，各种类型的值（包括对象）都可以当作键。也就是说，Object 结构提供了“字符串—值”的对应，Map 结构提供了“值—值”的对应，是一种更完善的 Hash 结构实现。如果你需要“键值对”的数据结构，Map 比 Object 更合适。

    // 如何创建Map数据  => 通过构造函数创建
    var m = new Map();
    console.log(m);


    // Map数据结构的属性和方法 
    // 属性:
    // size  => 返回map数据结构成员的个数( => 有几条数据)

    // 方法:
    // set(key,val)  对应键名设置键值 (没有就新增,有就修改)  返回值: 返回Map数据结构本身,可以接链式操作
    // get(key)      对应键名获取数据       返回值: 存在就返回键值 否则就返回 undefined
    // has(key)      判断是否存在某个键名    返回值: 存在=>true 不存在 => false
    // delete(key)   对应键名删除数据(单删)  返回值: 删除成功 => true 删除失败=>false
    // clear()       清除map数据结构 (清空所有数据  返回值: undefined)
    // forEach(function(val,key))     遍历Map数据结构  

    // 逐条新增
    // m.set(100,200);
    // m.set("hello","world");
    // m.set(true,false);
    // m.set(null,undefined);
    
    // var arr = [1,2,3];
    // var obj = {a:1,b:2};
    // m.set(arr,arr);
    // m.set(obj,obj);


    // var res = m.set(100,200);  
    // console.log("res",res); // 返回值: 新增数据后, Map数据结构本身

    // 链式语法 => 本质:方法的返回值还是相同类型的数据 (新的/原本的)
    var arr = [1,2,3];
    var obj = {a:1,b:2};
    m.set(100,200).set("hello","world").set(true,false).set(null,undefined).set(arr,arr).set(obj,obj);


    // console.log(m.get(100));
    // console.log(m.get("hello"));
    // console.log(m.get(true));
    // console.log(m.get(null));
    // console.log(m.get(arr));
    // console.log(m.get(obj));
    // console.log(m.get("abc"));  //  不存在属性就返回undefined

    // has(key)   是否存在对应键名
    // console.log(m.has(100));  // true
    // console.log(m.has("hello"));
    // console.log(m.has(true));
    // console.log(m.has(null));
    // console.log(m.has(arr));
    // console.log(m.has(obj));
    // console.log(m.has("abc"));  // false


    // delete(key)  对应键名删除 => 单删
    // console.log(m.delete(100));  // true
    // console.log(m.delete("hello"));
    // console.log(m.delete(true));
    // console.log(m.delete(null));
    // console.log(m.delete(arr));
    // console.log(m.delete(obj));
    // console.log(m.delete("abc"));  // false 

    // clear()  
    // console.log(m.clear());

    // forEach() 遍历方法
    // m.forEach(function(val,key){
    //     console.log(key,val);
    // })

    console.log(m);
    console.log(m.size);

</script>
</html>